<?php
namespace app\common\controller;
use think\Config;
//引用支付宝官方的demo
require('aop/AopClient.php');
require('aop/request/AlipayTradeAppPayRequest.php');
class Alipay
{

        /**
     * 生成用于调用收银台SDK的字符串
     * @param $request SDK接口的请求参数对象
     * @return string 
     * @author guofa.tgf
     */
    public function sdkExecute($request) {
        
        $this->setupCharsets($request);

        $config = get_addon_config('epay');
        $config = $config['alipay'];

        $params['app_id'] = $config['app_id'];
        $params['method'] = 'alipay.trade.app.pay';
        $params['format'] = $request['format']; 
        $params['sign_type'] = $request['sign_type'];
        $params['timestamp'] = $request['timestamp'];
        $params['alipay_sdk'] = "alipay-sdk-php-20161101";
        $params['charset'] = "utf-8";

        $params['version'] = $request['version'];

        $params['notify_url'] = $request['notify_url'];
        

        $params['biz_content'] = $request['biz_content'];

        ksort($params);

        $params['sign'] = $this->generateSign($params, 'RSA2');

        foreach ($params as &$value) {
            $value = $this->characet($value, $params['charset']);
        }
        
        return http_build_query($params);
    }
    public function generateSign($params, $signType = "RSA") {
        return $this->sign($this->getSignContent($params), $signType);
    }

    /**
     * 生成APP支付订单信息
     * @param $data
     * @return bool|string  返回支付宝签名后订单信息，否则返回false
     * @throws \Exception
     */
    public function generateOrder($data)
    {
        $config = get_addon_config('epay');
        $config = $config['alipay'];

        $aop = new \AopClient();
        $aop->gatewayUrl = 'https://openapi.alipay.com/gateway.do';
        $aop->appId = $config['app_id'];                      //APPID
        $aop->rsaPrivateKey = $config['private_key'];   //商户私钥
        $aop->alipayrsaPublicKey = $config['ali_public_key'];     //应用公钥
        $aop->apiVersion = $data['version'];
        $aop->signType = $data['sign_type'];
        $aop->postCharset = $data['charset'];
        $aop->format = $data['format'];
        $request = new \AlipayTradeAppPayRequest ();
        $request->setBizContent($data['biz_content']);
        $request->setNotifyUrl($data['notify_url']);
        $data['sign'] = $aop->makeSign($request);   //自己封装的支付宝sign签名
        return $this->getSignContent($data);   //数据格式化成字符串
    }
    /**
     * 签名处理
     * @param $params
     * @param $charset
     * @return string
     */
    private function getSignContent($params)
    {
        ksort($params);
        $stringToBeSigned = "";
        $i = 0;
        foreach ($params as $k => $v) {
            if (false === $this->checkEmpty($v) && "@" != substr($v, 0, 1)) {
                // 转换成目标字符集
                $v = $this->characet($v, $params['charset']);
                $v = urlencode($v);
                if ($i == 0) {
                    $stringToBeSigned .= "$k" . "=" . "$v";
                } else {
                    $stringToBeSigned .= "&" . "$k" . "=" . "$v";
                }
                $i++;
            }
        }
        unset ($k, $v);
        return $stringToBeSigned;
    }
    /**
     * 校验$value是否非空
     * @param $value
     * @return  boolean;
     *  if not set ,return true;
     *  if is null , return true;
     **/
    public function checkEmpty($value)
    {
        if (!isset($value))
            return true;
        if ($value === null)
            return true;
        if (trim($value) === "")
            return true;
        return false;
    }
    /**
     * 转换字符集编码
     * @param $data
     * @param $targetCharset
     * @return string
     */
    public function characet($data, $targetCharset)
    {
        if (!empty($data)) {
            $fileType = "UTF-8";
            if (strcasecmp($fileType, $targetCharset) != 0) {
                $data = mb_convert_encoding($data, $targetCharset, $fileType);
            }
        }
        return $data;
    }
}